home *** CD-ROM | disk | FTP | other *** search
/ PC World Komputer 2010 April / PCWorld0410.iso / hity wydania / Ubuntu 9.10 PL / karmelkowy-koliberek-9.10-netbook-remix-PL.iso / casper / filesystem.squashfs / usr / share / pyshared / nose / result.py < prev    next >
Encoding:
Python Source  |  2009-05-13  |  5.8 KB  |  176 lines

  1. """
  2. Test Result
  3. -----------
  4.  
  5. Provides a TextTestResult that extends unittest._TextTestResult to
  6. provide support for error classes (such as the builtin skip and
  7. deprecated classes), and hooks for plugins to take over or extend
  8. reporting.
  9. """
  10.  
  11. import logging
  12. from unittest import _TextTestResult
  13. from nose.config import Config
  14. from nose.util import isclass, ln as _ln # backwards compat
  15.  
  16. log = logging.getLogger('nose.result')
  17.  
  18.  
  19. def _exception_detail(exc):
  20.     # this is what stdlib module traceback does
  21.     try:
  22.         return str(exc)
  23.     except:
  24.         return '<unprintable %s object>' % type(exc).__name__
  25.  
  26.  
  27. class TextTestResult(_TextTestResult):
  28.     """Text test result that extends unittest's default test result
  29.     support for a configurable set of errorClasses (eg, Skip,
  30.     Deprecated, TODO) that extend the errors/failures/success triad.
  31.     """    
  32.     def __init__(self, stream, descriptions, verbosity, config=None,
  33.                  errorClasses=None):        
  34.         if errorClasses is None:
  35.             errorClasses = {}
  36.         self.errorClasses = errorClasses
  37.         if config is None:
  38.             config = Config()       
  39.         self.config = config
  40.         _TextTestResult.__init__(self, stream, descriptions, verbosity)
  41.                 
  42.     def addError(self, test, err):
  43.         """Overrides normal addError to add support for
  44.         errorClasses. If the exception is a registered class, the
  45.         error will be added to the list for that class, not errors.
  46.         """
  47.         stream = getattr(self, 'stream', None)
  48.         ec, ev, tb = err
  49.         try:
  50.             exc_info = self._exc_info_to_string(err, test)
  51.         except TypeError:
  52.             # 2.3 compat
  53.             exc_info = self._exc_info_to_string(err)
  54.         for cls, (storage, label, isfail) in self.errorClasses.items():
  55.             if isclass(ec) and issubclass(ec, cls):
  56.                 if isfail:
  57.                     test.passed = False
  58.                 storage.append((test, exc_info))
  59.                 # Might get patched into a streamless result
  60.                 if stream is not None:
  61.                     if self.showAll:
  62.                         message = [label]
  63.                         detail = _exception_detail(err[1])
  64.                         if detail:
  65.                             message.append(detail)
  66.                         stream.writeln(": ".join(message))
  67.                     elif self.dots:
  68.                         stream.write(label[:1])
  69.                 return
  70.         self.errors.append((test, exc_info))
  71.         test.passed = False
  72.         if stream is not None:
  73.             if self.showAll:
  74.                 self.stream.writeln('ERROR')
  75.             elif self.dots:
  76.                 stream.write('E')
  77.  
  78.     def printErrors(self):
  79.         """Overrides to print all errorClasses errors as well.
  80.         """
  81.         _TextTestResult.printErrors(self)
  82.         for cls in self.errorClasses.keys():
  83.             storage, label, isfail = self.errorClasses[cls]
  84.             if isfail:
  85.                 self.printErrorList(label, storage)
  86.         # Might get patched into a result with no config
  87.         if hasattr(self, 'config'):
  88.             self.config.plugins.report(self.stream)
  89.  
  90.     def printSummary(self, start, stop):
  91.         """Called by the test runner to print the final summary of test
  92.         run results.
  93.         """
  94.         write = self.stream.write
  95.         writeln = self.stream.writeln
  96.         taken = float(stop - start)
  97.         run = self.testsRun
  98.         plural = run != 1 and "s" or ""
  99.         
  100.         writeln(self.separator2)
  101.         writeln("Ran %s test%s in %.3fs" % (run, plural, taken))
  102.         writeln()
  103.  
  104.         summary = {}
  105.         eckeys = self.errorClasses.keys()
  106.         eckeys.sort()
  107.         for cls in eckeys:
  108.             storage, label, isfail = self.errorClasses[cls]
  109.             count = len(storage)
  110.             if not count:
  111.                 continue
  112.             summary[label] = count
  113.         if len(self.failures):
  114.             summary['failures'] = len(self.failures)
  115.         if len(self.errors):
  116.             summary['errors'] = len(self.errors)
  117.  
  118.         if not self.wasSuccessful():
  119.             write("FAILED")
  120.         else:
  121.             write("OK")
  122.         items = summary.items()
  123.         if items:
  124.             items.sort()
  125.             write(" (")
  126.             write(", ".join(["%s=%s" % (label, count) for
  127.                              label, count in items]))
  128.             writeln(")")
  129.         else:
  130.             writeln()
  131.  
  132.     def wasSuccessful(self):
  133.         """Overrides to check that there are no errors in errorClasses
  134.         lists that are marked as errors and should cause a run to
  135.         fail.
  136.         """
  137.         if self.errors or self.failures:
  138.             return False
  139.         for cls in self.errorClasses.keys():
  140.             storage, label, isfail = self.errorClasses[cls]
  141.             if not isfail:
  142.                 continue
  143.             if storage:
  144.                 return False
  145.         return True
  146.  
  147.     def _addError(self, test, err):
  148.         try:
  149.             exc_info = self._exc_info_to_string(err, test)
  150.         except TypeError:
  151.             # 2.3: does not take test arg
  152.             exc_info = self._exc_info_to_string(err)
  153.         self.errors.append((test, exc_info))
  154.         if self.showAll:
  155.             self.stream.write('ERROR')
  156.         elif self.dots:
  157.             self.stream.write('E')
  158.  
  159.     def _exc_info_to_string(self, err, test=None):
  160.         # 2.3/2.4 -- 2.4 passes test, 2.3 does not
  161.         try:
  162.             return _TextTestResult._exc_info_to_string(self, err, test)
  163.         except TypeError:
  164.             # 2.3: does not take test arg
  165.             return _TextTestResult._exc_info_to_string(self, err)
  166.  
  167.  
  168. def ln(*arg, **kw):
  169.     from warnings import warn
  170.     warn("ln() has moved to nose.util from nose.result and will be removed "
  171.          "from nose.result in a future release. Please update your imports ",
  172.          DeprecationWarning)
  173.     return _ln(*arg, **kw)
  174.     
  175.  
  176.